#include <myheader.h>

/*Usage:  */
int main(int argc, char *argv[])
{
    char *ip = "192.168.112.129";
    char *port = "8080";
    //create a socket 
    int socket_fd = socket(AF_INET,SOCK_STREAM,0);
    ERROR_CHECK(socket_fd,-1,"socket");

    //reuse port
    int optval = 1;
    int ret = setsockopt(socket_fd,SOL_SOCKET,SO_REUSEADDR,&optval,sizeof(optval));
    ERROR_CHECK(ret,-1,"setsockopt");

    //bind
    struct sockaddr_in sockaddr_in;
    sockaddr_in.sin_family = AF_INET;
    sockaddr_in.sin_port = htons(atoi(port));
    sockaddr_in.sin_addr.s_addr = inet_addr(ip);

    ret = bind(socket_fd,(struct sockaddr*)&sockaddr_in,
               sizeof(sockaddr_in));
    ERROR_CHECK(ret,-1,"bind");

    //listen
    ret = listen(socket_fd,10);
    ERROR_CHECK(ret,-1,"listen");

    //base_set, used to record all the fd
    fd_set base_set;
    FD_ZERO(&base_set);
    FD_SET(STDIN_FILENO,&base_set);
    FD_SET(socket_fd,&base_set);

    int net_fd = 0;
    char buf[60] = {0};
    while(1){
        //listen the stdin and socket_fd
        fd_set listen_while;
        memcpy(&listen_while,&base_set,sizeof(base_set));

        //find the max fd
        int maxfd = 0;
        for(int fd = 0; fd < FD_SETSIZE; fd++){
            if(FD_ISSET(fd,&listen_while)){
                maxfd = (fd > maxfd) ? fd : maxfd;
            }
        }
        select(maxfd + 1, &listen_while,NULL,NULL,NULL);

        //select
        if(FD_ISSET(socket_fd, &listen_while)){

            //accept
            net_fd = accept(socket_fd,NULL, NULL);
            ERROR_CHECK(net_fd,-1,"accept");

            //put the net_fd in base_set
            FD_ZERO(&base_set);
            FD_SET(net_fd,&base_set);
            FD_SET(STDIN_FILENO,&base_set);
        }

        if(FD_ISSET(net_fd,&listen_while)){

            //client send some msg
            memset(buf,0 ,sizeof(buf));
            int read_cnt = recv(net_fd,buf,sizeof(buf),0);
            ERROR_CHECK(read_cnt,-1,"recv");
            if(read_cnt == 0){
                //the other side disconnect
                FD_ZERO(&base_set);
                FD_SET(socket_fd,&base_set);
                continue;
            }

            printf("%s\n",buf);
        }

        if(FD_ISSET(STDIN_FILENO,&listen_while)){
            memset(buf,0,sizeof(buf));
            int read_cnt = read(STDIN_FILENO,buf,sizeof(buf));
            ERROR_CHECK(read_cnt,-1,"read_stdin");
   
            //send
            int send_cnt = send(net_fd,buf,sizeof(buf),0);
            ERROR_CHECK(send_cnt,-1,"send");
        }
    }

    return 0;
}

